#ifndef __STRING__
#define __STRING__

#include <string>
#include <algorithm> 
#include <functional> 
#include <cctype>
#include <locale>

class String
{
public:
	template<typename T>
	static inline T Split(const std::string &s, const std::string &delim, const bool keep_empty = true)
	{
		T result;
		
		if (delim.empty())
		{
			result.push_back(s);
			return result;
		}

		std::string::const_iterator substart = s.begin(), subend;

		while (true)
		{
			subend = search(substart, s.end(), delim.begin(), delim.end());
			std::string temp(substart, subend);

			if (keep_empty || !temp.empty())
				result.push_back(temp);

			if (subend == s.end())
				break;

			substart = subend + delim.size();
		}

		return result;
	}

	// trim from start
	static inline std::string &TrimStart(std::string &s)
	{
		s.erase(s.begin(), std::find_if(s.begin(), s.end(), std::not1(std::ptr_fun<int, int>(std::isspace))));
		return s;
	}

	// trim from end
	static inline std::string &TrimEnd(std::string &s)
	{
		s.erase(std::find_if(s.rbegin(), s.rend(), std::not1(std::ptr_fun<int, int>(std::isspace))).base(), s.end());
		return s;
	}

	// trim from both ends
	static inline std::string &Trim(std::string &s)
	{
		return TrimStart(TrimEnd(s));
	}
};
#endif